// Memory usage
// - Accumulated time values are stored in 24 bit numbers
// - the value is incremented every accumulated minute
// - each value is duplicated and stored with an 8 bit checksum
// - on startup the numbers are validated by reading them
// - an erroneous value is restored by copying from its twin
// - this means a single 24 bit value actually requires 8 bytes

// EECON1
// 0bWW0W WWSS
//   || | |||+-- RD: 1=Initiate Read
//   || | ||+--- WR: 1=Initiate Write, 0=Write complete
//   || | |+---- WREN: 1=Write Enable, 0=Write Disable
//   || | +----- WRERR: 1=Write Error, 0=Write OK
//   || +------- FREE: 1=Erase block, 0=Write 
//   |+--------- CFGS: 1=Access config block, 0=Acccess Data block
//   +---------- EEPGD: 1=Access Flash program, 0=Access EEPROM data

#define RUN_TIME		0
#define LB_LP_TIME	1

#define EE_WRITE_BUFFER_SIZE  16
#define EE_WRITE_BUFFER_MASK  0x0f

char eeWrData[EE_WRITE_BUFFER_SIZE];
char eeWrAddr[EE_WRITE_BUFFER_SIZE];
char eeWrStart, eeWrEnd;

char *ee_data;
char ee_count;

char chk_sum( char *data, char bytes )
{
   char checksum = *data++;
   
   while( --bytes )
      checksum += *data++;

   return( checksum );
}

char chk_generate( char *data, char bytes )
{
   W = chk_sum( data, bytes );
   return( negate(W) );
}

char chk_compare( char *data, char bytes, char checkByte )
{
   return( checkByte + chk_sum( data, bytes ) );
}

char ee_getchar( char addr )
{
	EEPGD = 0;
	CFGS = 0;
	EEADR = addr;
   RD = 1;
   return( EEDATA );
}

char ee_putchar( char data, char addr )
{
   // Check to see if buffer is full.
   // Indicated by start=end AND interrupt already enabled
   if( (eeWrStart == eeWrEnd) && (EEIE==1) )
      return 1;

   eeWrData[eeWrStart] = data;
   eeWrAddr[eeWrStart] = addr;

   eeWrStart = ++eeWrStart & EE_WRITE_BUFFER_MASK;
   
   if( EEIE == 0 )
   {
      EEIE = 1;
      ee_writeByte();
   }
   return( 0 );
}

// Check to see if write buffer is empty
// Indicated by interrupt disabled
// beacuse interrupt is enabled when something is in buffer
char ee_writeEmpty( void )
{
   if( EEIE==0 ) 
      return( 1 );
   return( 0 );
}

void isr_ee_write( void )
{
	EEIF = 0;
	WREN = 0;

   if( eeWrStart == eeWrEnd )
      EEIE = 0;
   else
      ee_writeByte();
}

void ee_writeByte( void )
{
   EEDATA = eeWrData[eeWrEnd];
   EEADR = eeWrAddr[eeWrEnd];
	EEADRH = 0;
	EEPGD = 0;
	CFGS = 0;
	WREN = 1;

	GIE = 0;
	
	EECON2 = 0x55;
	EECON2 = 0xaa;
	WR = 1;

	GIE = 1;

   eeWrEnd = ++eeWrEnd & EE_WRITE_BUFFER_MASK;
}
